//----BEGIN LICENSE----//
/*****************************************************************\
** prevalentLite - sqlite3 persistence object library 
**
** Copyright (C) 2008 Philip R. Schuchardt
**
** This program is free software: you can redistribute it and/or modify
** it under the terms of the GNU General Public License as published by
** the Free Software Foundation, either version 3 of the License, or
** (at your option) any later version.
**
** This program is distributed in the hope that it will be useful,
** but WITHOUT ANY WARRANTY; without even the implied warranty of
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
** GNU General Public License for more details.
**
** You should have received a copy of the GNU General Public License
** along with this program.  If not, see <http://www.gnu.org/licenses/>.
**
*****************************************************************/
//----END LICENSE----//
/*--------------------------------------------------------------------------
        The base class for data classes like plDouble, plString,
        plInt.
	
	By: Philip Schuchardt - 2008-10-26
-----------------------------------------------------------------------------*/

#ifndef plDATA_H
#define plDATA_H

//STL includes
#include <map>
#include <string>

//sqlite includes
#include <sqlite3.h>

//Our includes
class plObject;
class plDatabase;

class plData {
	
public:
	//Constructor
        plData();

	//Destructor
        virtual ~plData();

	//Copy constructor
        plData(const plData& data);

	//Gets the column name
        const std::string & GetColumnName() const;

	//Gets the table name
        const std::string& GetTableName() const;

	//Gets the owner object
        plObject* GetOwner() const;

	//Setups up the data
        void Setup(const std::string& columnName, plObject* owner);

	//True if the data is setup, and false if Setup() wasn't called
	bool IsSetup();
	
	//Causes this object not to try to commite to the database
	void SetDisabled(bool disabled) { Disabled = disabled; }

        /*!
        \brief Binds the data with a sqlite3 statement

        Should be reimplement in the subclass

        \param statement - The sqlite3 statement should be directly passed to sqlite3_bind() ... See sqlite3 documentation for details
        \param index - The index - Should be directly passed to sqlite3_bind() ... See sqlite3 documentation for details


        */
        virtual void Bind(sqlite3_stmt* /*statement*/, int /*index*/ = 1) const {}

        /*!
        \brief Extracts the data from the current columnName

        Should be reimplemented in the subclass

        \param statement - Used to get data from the statement ... See sqlite3_column() in the sqlite3 documentation for details
        \param index - Used to get data from the statement ... See sqlite3_column() in the sqlite3 documentation for details


        */
        virtual void Column(sqlite3_stmt* /*statement*/, int /*index*/ = 0) {}

        /*!
          \breif Gets the classname

            Should be overload by the subclass

          */
        static const char* GetClassName() { return "plData"; }
		
	//Get the Database
        static plDatabase* GetDatabase();

        //Gets the data from the database if need
        void GetData() const;

        //Sets the data in the database
        void SetData();

protected:
	bool Cached;
        bool Disabled;


private:
	
	//The perpose for this class is to reduce the ammout of memory used by
	//An object. The ColumnName, TableName, Owner are used statically 
	//By many of the same objects... This class allow these piece of data to
	//Be declare statically making data only hold one pointer to this class.
	class ReferanceData {
		public:
		//Constructor
		ReferanceData() {}
		
                std::string ColumnName;
                std::string TableName;
	};

	ReferanceData* Referance;
	
	//The static lookup of all the Referances
	static std::map<std::string, ReferanceData*> Lookup;

	//The class that owns me
        plObject* Owner;
	
	//Initializes the data
	void Init();

};

#endif //plDATA_H

